package com.springBoot.springBootSysCore.modules.services.system.impl;

import com.springBoot.springBootSysCore.common.StaticConfig;
import com.springBoot.springBootSysCore.common.service.IBaseServiceImpl;
import com.springBoot.springBootSysCore.common.utils.json.JsonUtil;
import com.springBoot.springBootSysCore.common.utils.returnUtil.CodeEnum;
import com.springBoot.springBootSysCore.common.utils.returnUtil.ResultJsonFormat;
import com.springBoot.springBootSysCore.modules.entity.system.*;
import com.springBoot.springBootSysCore.modules.entity.utils.UserUtils;
import com.springBoot.springBootSysCore.modules.enums.base.DeleteStateEnum;
import com.springBoot.springBootSysCore.modules.enums.base.MessageTypeEnum;
import com.springBoot.springBootSysCore.modules.repository.system.SysFaqRepository;
import com.springBoot.springBootSysCore.modules.repository.system.SysMessageLogRepository;
import com.springBoot.springBootSysCore.modules.repository.system.SysMessageRepository;
import com.springBoot.springBootSysCore.modules.services.system.SysFaqService;
import com.springBoot.springBootSysCore.modules.services.system.SysMessageService;
import org.apache.commons.collections.map.HashedMap;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.persistence.criteria.*;
import javax.servlet.http.HttpServletRequest;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Map;

/**
 * Created by timo on 2017/11/27.
 */
@Service
public class SysMessageServiceImpl extends IBaseServiceImpl<SysMessage, String> implements SysMessageService {
    @Autowired
    private SysMessageRepository sysMessageRepository;

    @Autowired
    private SysMessageLogRepository sysMessageLogRepository;

    @Override
    @Transactional
    public Map<String, Object> deleteEntity(SysMessage entity) {
        ResultJsonFormat rj = new ResultJsonFormat("删除成功", CodeEnum.SUCCESS.value());
        try {
            if (StringUtils.isNoneBlank(entity.getId())) {
                if (entity.isSureDel()) {
//					sysUserRepository.deleteById(user.getId());
                } else {
//					sysUserRepository.updateEntityById(user);
                }
            } else {
                String ids = "";
                String[] a = entity.getIds().split(",");
                for (int i = 0; i < a.length; i++) {
                    ids += "'" + a[i] + "'";
                    if (i != a.length - 1) {
                        ids += ",";
                    }
                }
                if (entity.isSureDel()) {
                    sysMessageRepository.deleteByIds(Arrays.asList(a));
                } else {
                    sysMessageRepository.updateDelFlag(Arrays.asList(a));
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
            throw e;
        }
        return rj.convertResultJson();
    }

    @Override
    public Map<String, Object> getPublicMessage(HttpServletRequest request, PageRequest buildPageRequest) {
        ResultJsonFormat ret = new ResultJsonFormat(CodeEnum.SUCCESS.value());
        try {
            String userName = request.getParameter(StaticConfig.PARAM_USERNAME);
            SysUser user = UserUtils.getByAccount(userName);
            Page<Object[]> page = sysMessageRepository.getPublicMessage(user.getId(), buildPageRequest);
            String[] li = new String[]{"id", "title", "describe", "details", "objId", "createDate", "readed"};
            List<Map<String, Object>> listMap = JsonUtil.castEntity(page.getContent(), li);
            ret = new ResultJsonFormat("查询成功", listMap, page.hasNext(), buildPageRequest.getPageNumber() + 1, buildPageRequest.getPageSize(), page.getTotalElements(), CodeEnum.SUCCESS.value());
        } catch (Exception e) {
            e.printStackTrace();
            ret.setFlag(CodeEnum.ERROR.value());
            ret.setMsg("系统错误");
        }
        return ret.convertResultJsonForData();
    }

    @Override
    public Map<String, Object> countMessage(HttpServletRequest request) {
        ResultJsonFormat rj = new ResultJsonFormat(CodeEnum.SUCCESS.value());
        try {
            Map<String, Object> m = new HashedMap();
           final SysUser user = UserUtils.getByAccount(request.getParameter(StaticConfig.PARAM_USERNAME));
            m.put("sysSize", sysMessageRepository.count(new Specification<SysMessage>() {
                @Override
                public Predicate toPredicate(Root<SysMessage> root, CriteriaQuery<?> criteriaQuery, CriteriaBuilder criteriaBuilder) {
                    List<Predicate> list = new ArrayList<Predicate>();
                    list.add(criteriaBuilder.equal(root.get("messAgeType").as(String.class), MessageTypeEnum.SYS.getVal()));
                    list.add(criteriaBuilder.equal(root.get("toSysUser").get("id"), user.getId()));
                    list.add(criteriaBuilder.isFalse(root.get("readed")));
                    list.add(criteriaBuilder.equal(root.get("delFlag").as(String.class), DeleteStateEnum.NO_DELETE.getVal()));
                    criteriaQuery.where(list.toArray(new Predicate[list.size()]));
                    ;
                    return criteriaQuery.getRestriction();
                }
            }));
            m.put("publicSize", sysMessageRepository.countPublicMessage(user.getId()));
            m.put("courseSize", sysMessageRepository.count(new Specification<SysMessage>() {
                @Override
                public Predicate toPredicate(Root<SysMessage> root, CriteriaQuery<?> criteriaQuery, CriteriaBuilder criteriaBuilder) {
                    List<Predicate> list = new ArrayList<Predicate>();
                    list.add(criteriaBuilder.equal(root.get("messAgeType").as(String.class), MessageTypeEnum.COURSE.getVal()));
                    list.add(criteriaBuilder.equal(root.get("toSysUser").get("id"), user.getId()));
                    list.add(criteriaBuilder.isFalse(root.get("readed")));
                    list.add(criteriaBuilder.equal(root.get("delFlag").as(String.class), DeleteStateEnum.NO_DELETE.getVal()));
                    criteriaQuery.where(list.toArray(new Predicate[list.size()]));
                    ;
                    return criteriaQuery.getRestriction();
                }
            }));
            rj.setData(m);
        } catch (Exception e) {
            e.printStackTrace();
            throw e;
        }
        return rj.convertResultJson();
    }

    @Override
    @Transactional
    public Map<String, Object> readAllMessage(HttpServletRequest request, String type) {
        ResultJsonFormat rj = new ResultJsonFormat(CodeEnum.SUCCESS.value());
        try {
            SysUser user = UserUtils.getByAccount(request.getParameter(StaticConfig.PARAM_USERNAME));

            if (!type.equals(MessageTypeEnum.NOTICE.getVal())) {
                sysMessageRepository.readMessageByType(user.getId(), type);
            } else {
                List<String> li = sysMessageRepository.getPublicMessage(user.getId());
                for (String mId : li) {
                    SysMessage m = sysMessageRepository.findOne(mId);
                    m.setReaded(true);
                    SysMessageLog ml = new SysMessageLog();
                    ml.setReaded(true);
                    ml.preInsert();
                    ml.setSysUser(user);
                    ml.setSysMessage(m);
                    sysMessageLogRepository.save(ml);
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
            throw e;
        }
        return rj.convertResultJson();
    }

    @Override
    @Transactional
    public Map<String, Object> readMessage(HttpServletRequest request, String id) {
        ResultJsonFormat rj = new ResultJsonFormat(CodeEnum.SUCCESS.value());
        try {
            SysMessage mes = sysMessageRepository.findOne(id);
            if (MessageTypeEnum.NOTICE.getVal().equals(mes.getMessAgeType())) {
                SysMessageLog ml = new SysMessageLog();
                ml.setReaded(true);
                ml.preInsert();
                ml.setSysUser(UserUtils.getByAccount(request.getParameter(StaticConfig.PARAM_USERNAME)));
                ml.setSysMessage(mes);
                sysMessageLogRepository.save(ml);
            } else {
                mes.setReaded(true);
                mes.preUpdate();
            }
        } catch (Exception e) {
            e.printStackTrace();
            throw e;
        }
        return rj.convertResultJson();
    }

    @Override
    @Transactional
    public Map<String, Object> deleteMessage(HttpServletRequest request, String id) {
        ResultJsonFormat rj = new ResultJsonFormat(CodeEnum.SUCCESS.value());
        try {
            SysMessage sysm = sysMessageRepository.findOne(id);
            if (MessageTypeEnum.NOTICE.getVal().equals(sysm.getMessAgeType())) {
                SysMessageLog ml = sysMessageLogRepository.findBySysUserIdAndSysMessageId(UserUtils.getByAccount(request.getParameter(StaticConfig.PARAM_USERNAME)).getId(), id);
                if (ml == null) {
                    ml = new SysMessageLog();
                    ml.setReaded(true);
                    ml.preInsert();
                    ml.setSysUser(UserUtils.getByAccount(request.getParameter(StaticConfig.PARAM_USERNAME)));
                    ml.setSysMessage(sysm);
                    ml = sysMessageLogRepository.save(ml);
                }
                ml.setDelFlag(DeleteStateEnum.YES_DELETE.getVal());
            } else {
                sysMessageRepository.delete(id);
            }
        } catch (Exception e) {
            e.printStackTrace();
            throw e;
        }
        return rj.convertResultJson();
    }


    @Override
    @Transactional
    public Map<String, Object> save(SysMessage entity) {
        ResultJsonFormat rj = new ResultJsonFormat("保存成功", CodeEnum.SUCCESS.value());
        try {
            entity.setMessAgeType(MessageTypeEnum.NOTICE.getVal());
            //此处检查参数是否规范
            if (StringUtils.isBlank(entity.getId())) {
                rj.isAdd();
                entity.preInsert();
                super.saveEntiey(entity);
            } else {
                entity.preUpdate();
                super.saveEntiey(entity);
            }
        } catch (Exception e) {
            e.printStackTrace();
            throw e;
        }
        return rj.convertResultJson();
    }
}
